#pragma once

#include <condition_variable>
#include <mutex>

class Semaphare {
public:
  Semaphare() = default;
  Semaphare(int limit) : resLimit_(limit) {}
  ~Semaphare() = default;

public:
  // P
  void wait() {
    std::unique_lock<std::mutex> lock(mtx_);
    cond_.wait(lock, [&](){return resLimit_ > 0;});
    resLimit_--;
  }
  // v
  void post() {
    std::unique_lock<std::mutex> lock(mtx_);
    resLimit_++;
    cond_.notify_all();
  }

private:
  int resLimit_{};
  std::mutex mtx_;
  std::condition_variable cond_;
};